﻿using UnityEngine;
using UnityEngine.EventSystems;

namespace Jinndev.UI {

    public class UILayer : BaseBehaviour, IEscape, IChangeLayer {

        public GameObject modalMask;
        public GameObject background;
        public GameObject foreground;
        public RectTransform content;

        public GameObject Child { get; private set; }
        public UIParam Param { get; private set; }

        public void Init(UIParam param, GameObject child) {
            Param = param == null ? new UIParam() : param;
            Child = child;

            child.transform.SetParent(content, false);

            //BaseBehaviour childBehaviour = child.GetComponent<BaseBehaviour>();
            //if (childBehaviour != null) {
            //    childBehaviour.onInvokeDestroy += OnChildDestroy;
            //}
            //else {
            //    DestroyCallback.Add(child, OnChildDestroy, "UILayer.OnChildDestroy");
            //}
            DestroyCallback.Add(Child, OnChildDestroy, "UILayer.OnChildDestroy");

            modalMask.SetActive(Param.modal || Param.docb);
            background.SetActive(Param.mask);
            foreground.SetActive(false);
        }

        private void OnDestroy() {
            Child = null;
        }

        private void OnChildDestroy() {
            Child = null;
            base.Destroy();
        }

        public override void Destroy() {
            if (Child != null) {
                //BaseBehaviour childBehaviour = Child.GetComponent<BaseBehaviour>();
                //if (childBehaviour != null) {
                //    childBehaviour.onInvokeDestroy -= OnChildDestroy;
                //    childBehaviour.Destroy(); // 为了能触发child的Destory
                //}
                //else {
                //    Child.GetComponent<DestroyCallback>().callback -= OnChildDestroy;
                //}
                DestroyCallback.Remove(Child, OnChildDestroy, "UILayer.OnChildDestroy");
                Child = null;
            }
            base.Destroy();
        }

        public void ToggleMask(bool show) {
            background.SetActive(show);
        }

        public void OnLeftClickBackground(Vector2 position) {
            OnClickBackground(PointerEventData.InputButton.Left, position);
        }

        public void OnMiddleClickBackground(Vector2 position) {
            OnClickBackground(PointerEventData.InputButton.Middle, position);
        }

        public void OnRightClickBackground(Vector2 position) {
            OnClickBackground(PointerEventData.InputButton.Right, position);
        }

        public void OnClickBackground(PointerEventData.InputButton button, Vector2 position) {
            bool enableDestroy = true;
            try {
                if (Child != null) {
                    IBackground background = Child.GetComponent<IBackground>();
                    if (background != null) {
                        enableDestroy = background.OnClickBackground(button, position);
                    }
                }
            }
            catch (System.Exception e) {
                Debug.LogException(e);
            }

            if (Param.docb && enableDestroy) {
                Destroy();
            }
        }

        public EscapeResult OnEscape() {
            try {
                if (Child != null) {
                    IEscape escape = Child.GetComponent<IEscape>();
                    if (escape != null) {
                        return escape.OnEscape();
                    }
                }
            }
            catch (System.Exception e) {
                Debug.LogException(e);
            }
            return EscapeResult.Pass;
        }

        public void OnCover() {
            try {
                if (Child != null) {
                    IChangeLayer changeLayer = Child.GetComponent<IChangeLayer>();
                    if (changeLayer != null) {
                        changeLayer.OnCover();
                    }
                }
            }
            catch (System.Exception e) {
                Debug.LogException(e);
            }
        }

        public void OnTop() {
            try {
                if (Child != null) {
                    IChangeLayer changeLayer = Child.GetComponent<IChangeLayer>();
                    if (changeLayer != null) {
                        changeLayer.OnTop();
                    }
                }
            }
            catch (System.Exception e) {
                Debug.LogException(e);
            }
        }

        public void OnActivation() {
            try {
                if (Child != null) {
                    IActivation activation = Child.GetComponent<IActivation>();
                    if (activation != null) {
                        activation.OnActivation();
                    }
                }
            }
            catch (System.Exception e) {
                Debug.LogException(e);
            }
        }

        public void OnDeactivation() {
            try {
                if (Child != null) {
                    IActivation activation = Child.GetComponent<IActivation>();
                    if (activation != null) {
                        activation.OnDeactivation();
                    }
                }
            }
            catch (System.Exception e) {
                Debug.LogException(e);
            }
        }

    }

}
